package me.zhengjie.modules.hanzi.service.impl;

import com.alibaba.fastjson.JSON;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import me.zhengjie.modules.hanzi.dto.HanziAiScoreResult;
import me.zhengjie.modules.hanzi.service.AiServiceManager;
import me.zhengjie.modules.hanzi.service.HanziAiScoreService;
import me.zhengjie.modules.hanzi.service.HanziService;
import org.springframework.ai.chat.client.ChatClient;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;

import javax.imageio.ImageIO;
import java.awt.image.BufferedImage;
import java.io.IOException;
import java.util.HashMap;
import java.util.Map;

/**
 * Spring AI汉字评分服务实现类
 */
@Service
@RequiredArgsConstructor
@Slf4j
public class HanziAiScoreServiceImpl implements HanziAiScoreService {

    private final ChatClient chatClient; // 保留作为本地服务的后备
    private final HanziService hanziService;
    private final AiServiceManager aiServiceManager; // 新增AI服务管理器

    /**
     * AI评分系统的核心提示词（适配LM Studio, 纯文本模式）
     */
    private static final String HANZI_SCORING_PROMPT_TEXT_ONLY = """            
            你是一位专业的汉字书法评分专家，请根据提供的目标汉字和用户书写情况描述进行评分。
            
            目标汉字：{targetChar}
            用户书写情况：{writingDescription}
            
            请从以下维度进行评分（每项满分100分）：
            
            1. 字形准确度 (character_accuracy)：
               - 评估用户书写的汉字与标准字形的相似程度
               - 检查笔画是否正确、位置是否准确
               - 分析是否有笔画遗漏或多余
            
            2. 笔画规范度 (stroke_standard)：
               - 评估笔画的书写规范性
               - 检查笔画的起笔、行笔、收笔是否标准
               - 分析笔画的粗细变化是否合理
            
            3. 结构协调性 (structure_balance)：
               - 评估汉字各部分的比例关系
               - 检查左右、上下结构的平衡性
               - 分析整体布局是否协调
            
            4. 整体美观度 (overall_beauty)：
               - 评估书写的整体视觉效果
               - 检查字体的端正程度
               - 分析书写的流畅性和自然度
            
            请严格按照以下JSON格式返回评分结果，不要添加任何其他文字：
            
            {
              "total_score": <总分0-100>,
              "character_accuracy": <字形准确度0-100>,
              "stroke_standard": <笔画规范度0-100>,
              "structure_balance": <结构协调性0-100>,
              "overall_beauty": <整体美观度0-100>,
              "detailed_feedback": "<详细的评价内容，指出具体的优点和不足>",
              "improvement_suggestions": "<具体的改进建议，告诉用户如何提高书写质量>",
              "grade_level": "<根据总分给出等级：90-100为优秀，80-89为良好，70-79为中等，60-69为及格，60以下为需要改进>"
            }
            
            评分标准：
            - 90-100分：书写非常优秀，基本无瑕疵
            - 80-89分：书写良好，有小瑕疵但不影响整体
            - 70-79分：书写中等，有明显可改进之处
            - 60-69分：书写及格，需要加强练习
            - 60分以下：需要重点改进，多加练习
            
            请根据描述的书写情况，结合目标汉字的特点，给出客观、专业的评分和建议。
            """;

    /**
     * AI评分系统的核心提示词（支持图片输入模式）
     */
    private static final String HANZI_SCORING_PROMPT_WITH_IMAGE = """
            你是一位专业的汉字书法评分专家。请分析我提供的这张图片，图片内容是用户书写的汉字。
            
            目标汉字是：{targetChar}
            
            请直接根据图片中的书写情况，从以下维度进行评分（每项满分100分）：
            
            1. 字形准确度 (character_accuracy)
            2. 笔画规范度 (stroke_standard)
            3. 结构协调性 (structure_balance)
            4. 整体美观度 (overall_beauty)
            
            请严格按照以下JSON格式返回评分结果，不要添加任何其他文字：
            
            {
              "total_score": <总分0-100>,
              "character_accuracy": <字形准确度0-100>,
              "stroke_standard": <笔画规范度0-100>,
              "structure_balance": <结构协调性0-100>,
              "overall_beauty": <整体美观度0-100>,
              "detailed_feedback": "<详细的评价内容，指出具体的优点和不足>",
              "improvement_suggestions": "<具体的改进建议，告诉用户如何提高书写质量>",
              "grade_level": "<根据总分给出等级：90-100为优秀，80-89为良好，70-79为中等，60-69为及格，60以下为需要改进>"
            }
            """;

    /**
     * 构建纯文本评分提示词
     */
    private String buildTextOnlyScoringPrompt(String targetChar, String writingDescription) {
        return HANZI_SCORING_PROMPT_TEXT_ONLY
            .replace("{targetChar}", targetChar)
            .replace("{writingDescription}", writingDescription);
    }

    /**
     * 构建图片评分提示词
     */
    private String buildImageScoringPrompt(String targetChar) {
        return HANZI_SCORING_PROMPT_WITH_IMAGE.replace("{targetChar}", targetChar);
    }

    @Override
    public Map<String, Object> scoreWithAI(String targetChar, MultipartFile userImage) {
        Map<String, Object> result = new HashMap<>();
        String writingDescription = "（未使用图片转文字描述）"; // 默认值
        
        try {
            // 1. 使用AI服务管理器进行评分（自动处理图片或文本）
            log.info("开始调用AI对汉字 '{}' 进行评分", targetChar);
            
            // 准备提示词和图片
            String imagePrompt = buildImageScoringPrompt(targetChar);
            
            // 调用新的AiServiceManager方法，它会根据配置决定如何处理图片
            String aiResponse = aiServiceManager.callAiService(imagePrompt, userImage);

            // 如果aiResponse为空，说明AI服务可能不支持图片，或者失败了
            // 在这种情况下，我们回退到旧的文本描述方法
            if (aiResponse == null || aiResponse.trim().isEmpty()) {
                log.warn("AI服务（图片模式）返回空或调用失败，尝试回退到纯文本模式");
                
                // 1. (旧逻辑) 分析图像特征，生成文字描述
                writingDescription = analyzeImageFeatures(userImage, targetChar);
                
                // 2. (旧逻辑) 构建纯文本提示词并调用AI
                String textPrompt = buildTextOnlyScoringPrompt(targetChar, writingDescription);
                aiResponse = aiServiceManager.callAiService(textPrompt); // 仅传递文本
            }
            
            log.info("AI评分响应: {}", aiResponse);
            
            // 检查AI响应是否为空
            if (aiResponse == null || aiResponse.trim().isEmpty()) {
                log.warn("AI返回空响应，使用默认评分结果");
                return createDefaultScoreResult(targetChar, "AI服务暂时不可用，返回默认评分");
            }
            
            // 4. 解析AI返回的JSON结果
            HanziAiScoreResult scoreResult = parseAiResponse(aiResponse);
            
            // 5. 构建返回结果
            result.put("success", true);
            result.put("targetChar", targetChar);
            result.put("totalScore", scoreResult.getTotalScore());
            result.put("characterAccuracy", scoreResult.getCharacterAccuracy());
            result.put("strokeStandard", scoreResult.getStrokeStandard());
            result.put("structureBalance", scoreResult.getStructureBalance());
            result.put("overallBeauty", scoreResult.getOverallBeauty());
            result.put("detailedFeedback", scoreResult.getDetailedFeedback());
            result.put("improvementSuggestions", scoreResult.getImprovementSuggestions());
            result.put("gradeLevel", scoreResult.getGradeLevel());
            result.put("evaluationMethod", "HYBRID_AI_ANALYSIS"); // 更新评估方法名称
            result.put("writingDescription", writingDescription); // 添加图像分析结果
            
            return result;
            
        } catch (Exception e) {
            log.error("AI评分过程中发生错误", e);
            result.put("success", false);
            result.put("error", "AI评分失败: " + e.getMessage());
            return result;
        }
    }

    /**
     * 分析图像特征，生成文字描述供不支持图片的AI分析
     */
    private String analyzeImageFeatures(MultipartFile imageFile, String targetChar) throws IOException {
        // 读取图像
        BufferedImage image = ImageIO.read(imageFile.getInputStream());
        
        // 进行基本的图像分析
        int width = image.getWidth();
        int height = image.getHeight();
        
        // 计算黑色像素数量和分布
        int blackPixels = 0;
        int centerBlackPixels = 0;
        int leftBlackPixels = 0;
        int rightBlackPixels = 0;
        int topBlackPixels = 0;
        int bottomBlackPixels = 0;
        
        for (int x = 0; x < width; x++) {
            for (int y = 0; y < height; y++) {
                int rgb = image.getRGB(x, y);
                // 检查是否为黑色或深色像素
                if (isBlackOrDarkPixel(rgb)) {
                    blackPixels++;
                    
                    // 区域分析
                    if (x >= width/3 && x <= 2*width/3 && y >= height/3 && y <= 2*height/3) {
                        centerBlackPixels++;
                    }
                    if (x < width/2) leftBlackPixels++;
                    if (x >= width/2) rightBlackPixels++;
                    if (y < height/2) topBlackPixels++;
                    if (y >= height/2) bottomBlackPixels++;
                }
            }
        }
        
        // 计算特征比例
        double blackRatio = (double) blackPixels / (width * height);
        double centerRatio = (blackPixels > 0) ? (double) centerBlackPixels / blackPixels : 0;
        double leftRightBalance = (blackPixels > 0) ? Math.abs((double)(leftBlackPixels - rightBlackPixels)) / blackPixels : 0;
        double topBottomBalance = (blackPixels > 0) ? Math.abs((double)(topBlackPixels - bottomBlackPixels)) / blackPixels : 0;
        
        // 生成描述文本
        StringBuilder description = new StringBuilder();
        description.append(String.format("用户书写的汉字'%s'具有以下特征：", targetChar));
        
        // 笔画浓度分析
        if (blackRatio < 0.1) {
            description.append("笔画较细，可能存在笔画不够清楚或缺失的情况。");
        } else if (blackRatio > 0.3) {
            description.append("笔画较粗，可能存在笔迹过重或模糊的情况。");
        } else {
            description.append("笔画粗细适中，笔迹清晰。");
        }
        
        // 结构平衡分析
        if (centerRatio > 0.6) {
            description.append("字体结构集中，主要笔画位于中心区域。");
        } else {
            description.append("字体结构较为分散，笔画分布在较大范围内。");
        }
        
        // 左右平衡分析
        if (leftRightBalance < 0.1) {
            description.append("左右结构平衡性良好。");
        } else if (leftRightBalance < 0.3) {
            description.append("左右结构略有不平衡。");
        } else {
            description.append("左右结构明显不平衡。");
        }
        
        // 上下平衡分析
        if (topBottomBalance < 0.1) {
            description.append("上下结构平衡性良好。");
        } else if (topBottomBalance < 0.3) {
            description.append("上下结构略有不平衡。");
        } else {
            description.append("上下结构明显不平衡。");
        }
        
        // 添加数值信息供参考
        description.append(String.format("（技术参数：笔迹密度%.2f%%，中心集中度%.2f%%，左右偏移%.2f%%，上下偏移%.2f%%）", 
            blackRatio * 100, centerRatio * 100, leftRightBalance * 100, topBottomBalance * 100));
        
        return description.toString();
    }
    
    /**
     * 创建默认评分结果
     */
    private Map<String, Object> createDefaultScoreResult(String targetChar, String errorMessage) {
        Map<String, Object> result = new HashMap<>();
        result.put("success", true);
        result.put("targetChar", targetChar);
        result.put("totalScore", 60);
        result.put("characterAccuracy", 60);
        result.put("strokeStandard", 60);
        result.put("structureBalance", 60);
        result.put("overallBeauty", 60);
        result.put("detailedFeedback", "系统检测到您的书写，由于AI服务暂时不可用，无法提供详细评价。");
        result.put("improvementSuggestions", "建议检查网络连接或稍后重试。");
        result.put("gradeLevel", "及格");
        result.put("evaluationMethod", "DEFAULT_FALLBACK");
        result.put("writingDescription", errorMessage);
        return result;
    }
    /**
     * 判断像素是否为黑色或深色
     */
    private boolean isBlackOrDarkPixel(int rgb) {
        int red = (rgb >> 16) & 0xFF;
        int green = (rgb >> 8) & 0xFF;
        int blue = rgb & 0xFF;
        
        // 计算亮度，低于阈值则认为是深色像素
        int brightness = (int)(0.299 * red + 0.587 * green + 0.114 * blue);
        return brightness < 128; // 阈值可以根据需要调整
    }

    /**
     * 解析AI返回的JSON响应
     */
    private HanziAiScoreResult parseAiResponse(String aiResponse) {
        try {
            // 清理响应内容，移除可能的代码标记
            String cleanResponse = aiResponse.trim();
            if (cleanResponse.startsWith("```json")) {
                cleanResponse = cleanResponse.substring(7);
            }
            if (cleanResponse.endsWith("```")) {
                cleanResponse = cleanResponse.substring(0, cleanResponse.length() - 3);
            }
            cleanResponse = cleanResponse.trim();
            
            // 解析JSON
            return JSON.parseObject(cleanResponse, HanziAiScoreResult.class);
        } catch (Exception e) {
            log.error("解析本地AI响应失败: {}", aiResponse, e);
            // 返回默认结果
            HanziAiScoreResult defaultResult = new HanziAiScoreResult();
            defaultResult.setTotalScore(60);
            defaultResult.setCharacterAccuracy(60);
            defaultResult.setStrokeStandard(60);
            defaultResult.setStructureBalance(60);
            defaultResult.setOverallBeauty(60);
            defaultResult.setDetailedFeedback("本地AI解析失败，请检查模型配置或重试");
            defaultResult.setImprovementSuggestions("建议检查LM Studio连接状态或重新上传图片");
            defaultResult.setGradeLevel("需要改进");
            return defaultResult;
        }
    }
}
